#include "unity.h"
#include "mock_bsp_test_commom.h" // CMock 生成的 mock 头文件
#include "Rt_LUT_Config.h"

// test_XRt1553B_BCSTFromSubAddr.c

void setUp(void)
{
    // Set up before each test
}

void tearDown(void)
{
    // Clean up after each test
}

// Test case 1: Request more bytes than available
void test_XRt1553B_BCSTFromSubAddr_Should_ReturnZero_When_ByteLengthExceedsAvailable(void)
{
    // Arrange
    XRt1553B instance;
    u8 data[10];
    u32 subAddr = 5;

    instance.bcst_SAcfg[subAddr].valid_data_bytes = 4;

    // Act
    u32 result = XRt1553B_BCSTFromSubAddr(&instance, subAddr, data, 6);

    // Assert
    TEST_ASSERT_EQUAL_UINT32(0, result);
}

// Test case 2: Even byte length
void test_XRt1553B_BCSTFromSubAddr_Should_ReadCorrectData_When_EvenByteLength(void)
{
    // Arrange
    XRt1553B instance;
    u16 data[10] = {0};
    u32 subAddr = 5;
    u32 byteLength = 6;
    u32 wordLength = byteLength / 2;
    u32 startPtr = 0x2000;

    instance.BaseAddress = 0x1000;
    instance.bcst_SAcfg[subAddr].valid_data_bytes = byteLength;
    instance.bcst_SAcfg[subAddr].DataBlock_start_ptr = startPtr;
    instance.bcst_SAcfg[subAddr].mm_mode = XRT53_MM_SINGLE_MSG; // Not circular buffer

    // Expect memory reads
    for (u32 i = 0; i < wordLength; i++)
    {
        XRt1553B_ReadMem_ExpectAndReturn(instance.BaseAddress, startPtr + i, 0x1234 + i);
    }

    // Act
    u32 result = XRt1553B_BCSTFromSubAddr(&instance, subAddr, (u8 *)data, byteLength);

    // Assert
    TEST_ASSERT_EQUAL_UINT32(byteLength, result);
    for (u32 i = 0; i < wordLength; i++)
    {
        TEST_ASSERT_EQUAL_UINT16(0x1234 + i, data[i]);
    }
}

// Test case 3: Odd byte length
void test_XRt1553B_BCSTFromSubAddr_Should_ReadCorrectData_When_OddByteLength(void)
{
    // Arrange
    XRt1553B instance;
    u16 data[10] = {0};
    u32 subAddr = 5;
    u32 byteLength = 7;
    u32 expectedByteLength = 6; // 7-1=6, 6/2=3 words
    u32 wordLength = expectedByteLength / 2;
    u32 startPtr = 0x2000;

    instance.BaseAddress = 0x1000;
    instance.bcst_SAcfg[subAddr].valid_data_bytes = byteLength;
    instance.bcst_SAcfg[subAddr].DataBlock_start_ptr = startPtr;
    instance.bcst_SAcfg[subAddr].mm_mode = 0; // Not circular buffer

    // Expect memory reads
    for (u32 i = 0; i < wordLength; i++)
    {
        XRt1553B_ReadMem_ExpectAndReturn(instance.BaseAddress, startPtr + i, 0x5678 + i);
    }

    // Act
    u32 result = XRt1553B_BCSTFromSubAddr(&instance, subAddr, (u8 *)data, byteLength);

    // Assert
    TEST_ASSERT_EQUAL_UINT32(expectedByteLength, result);
    for (u32 i = 0; i < wordLength; i++)
    {
        TEST_ASSERT_EQUAL_UINT16(0x5678 + i, data[i]);
    }
}

// Test case 4: Circular buffer mode
void test_XRt1553B_BCSTFromSubAddr_Should_ResetPointers_When_CircularBufferMode(void)
{
    // Arrange
    XRt1553B instance;
    u16 data[10] = {0};
    u32 subAddr = 5;
    u32 byteLength = 4;
    u32 startPtr = 0x3000;

    instance.BaseAddress = 0x1000;
    instance.bcst_SAcfg[subAddr].valid_data_bytes = byteLength;
    instance.bcst_SAcfg[subAddr].DataBlock_start_ptr = startPtr;
    instance.bcst_SAcfg[subAddr].mm_mode = XRT53_MM_CIRCULAR_BUFFER;

    // Expect memory reads
    u32 wordLength = byteLength / 2;
    for (u32 i = 0; i < wordLength; i++)
    {
        XRt1553B_ReadMem_ExpectAndReturn(instance.BaseAddress, startPtr + i, 0x9ABC + i);
    }

    // Expect memory writes
    XRt1553B_WriteMem_Expect(instance.BaseAddress, XRT53_LUT_A_BCST(subAddr), startPtr);
    XRt1553B_WriteMem_Expect(instance.BaseAddress, XRT53_LUT_B_BCST(subAddr), startPtr);

    // Act
    u32 result = XRt1553B_BCSTFromSubAddr(&instance, subAddr, (u8 *)data, byteLength);

    // Assert
    TEST_ASSERT_EQUAL_UINT32(byteLength, result);
}

// Test case 5: Non-circular buffer mode
void test_XRt1553B_BCSTFromSubAddr_Should_NotResetPointers_When_NotCircularBufferMode(void)
{
    // Arrange
    XRt1553B instance;
    u16 data[10] = {0};
    u32 subAddr = 5;
    u32 byteLength = 4;
    u32 startPtr = 0x2000;

    instance.BaseAddress = 0x1000;
    instance.bcst_SAcfg[subAddr].valid_data_bytes = byteLength;
    instance.bcst_SAcfg[subAddr].DataBlock_start_ptr = startPtr;
    instance.bcst_SAcfg[subAddr].mm_mode = 0; // Not circular buffer

    // Expect memory reads
    u32 wordLength = byteLength / 2;
    for (u32 i = 0; i < wordLength; i++) {
        XRt1553B_ReadMem_ExpectAndReturn(instance.BaseAddress, startPtr + i, 0xDEF0 + i);
    }

    // Act
    u32 result = XRt1553B_BCSTFromSubAddr(&instance, subAddr, (u8*)data, byteLength);

    // Assert
    TEST_ASSERT_EQUAL_UINT32(byteLength, result);
}